package cn.maihe.elg.operation.centers.fuzhou.channel;

import cn.maihe.elg.operation.centers.fuzhou.auth.FZCenterAuthConfig;
import cn.maihe.elg.operation.centers.fuzhou.auth.FZHeaderInfo;
import cn.maihe.elg.operation.centers.fuzhou.config.FZMakeInfoConfig;
//import cn.maihe.elg.operation.centers.fuzhou.config.RestTemplateConfig;
import cn.maihe.elg.operation.centers.fuzhou.dto.FZBaseReqDTO;
import cn.maihe.elg.operation.centers.fuzhou.dto.FZBaseRespDTO;
import cn.maihe.elg.operation.centers.fuzhou.enums.FZChannelMethod;
import cn.maihe.elg.operation.centers.fuzhou.enums.HyMakeRespCodeEnum;
import cn.maihe.elg.operation.common.TradeContext;
import cn.maihe.elg.operation.exception.CenterException;
import cn.maihe.elg.operation.model.dto.BaseResp;
import cn.maihe.elg.operation.model.enums.CenterNoEnum;
import cn.maihe.elg.operation.model.enums.DelFlagEnum;
import cn.maihe.elg.operation.model.enums.InnerRespCode;
import cn.maihe.elg.operation.repository.entity.ExchangeCenterDO;
import cn.maihe.elg.operation.repository.entity.OrganizationDO;
import cn.maihe.elg.operation.service.business.ExchangeCenterService;
import cn.maihe.elg.operation.utils.*;
import cn.maihe.framework.starter.mybatis.dao.MybatisDaoImpl;
import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONObject;
import com.fasterxml.jackson.databind.DeserializationFeature;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.fasterxml.jackson.databind.SerializationFeature;
import com.google.common.cache.Cache;
import com.google.common.cache.CacheBuilder;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.springframework.cglib.beans.BeanMap;
import org.springframework.core.io.FileSystemResource;
import org.springframework.http.HttpEntity;
import org.springframework.http.HttpHeaders;
import org.springframework.http.MediaType;
import org.springframework.http.ResponseEntity;
import org.springframework.stereotype.Service;
import org.springframework.util.LinkedMultiValueMap;
import org.springframework.util.MultiValueMap;
import org.springframework.web.client.RestTemplate;

import javax.annotation.Resource;
import java.lang.reflect.ParameterizedType;
import java.math.BigDecimal;
import java.math.RoundingMode;
import java.net.SocketTimeoutException;
import java.security.KeyManagementException;
import java.security.KeyStoreException;
import java.security.NoSuchAlgorithmException;
import java.util.HashMap;
import java.util.Map;
import java.util.concurrent.TimeUnit;

/**
 * @Description 请求海迈中心基类服务
 * @Author WJH
 * @Date 2021/04/20
 */
@Service
@Slf4j
public abstract class FZBaseChannelService<REQ extends FZBaseReqDTO, RESP extends BaseResp> {

    @Resource
    private RestTemplate restTemplate;
    @Resource
    protected FZMakeInfoConfig fzMakeInfoConfig;
    @Resource
    private ExchangeCenterService exchangeCenterService;

    private final ObjectMapper objectMapper = new ObjectMapper();
    protected final Class<RESP> respClass;


    public FZBaseChannelService() {
        respClass = (Class) ((ParameterizedType) this.getClass().getGenericSuperclass()).getActualTypeArguments()[1];
        objectMapper.configure(SerializationFeature.FAIL_ON_EMPTY_BEANS, false);
        objectMapper.configure(DeserializationFeature.FAIL_ON_UNKNOWN_PROPERTIES, false);
    }

    /**
     * 设置公共字段：method&timestamp
     */
    protected REQ buildReq(REQ req, FZCenterAuthConfig authConfig) {
        return req;
    }

    /**
     * 实际请求url
     */
    private String buildReqUrl(FZCenterAuthConfig authConfig) {
        String reUrl = null;
        String url = authConfig.getCenterInfo().getUrl().trim();
        if (url.endsWith("/")) {
            reUrl = url + methodEnum().getMethod();
        } else {
            reUrl = url + "/" + methodEnum().getMethod();
        }
        //若有特殊配置指定地址则已指定地址为准
        if (methodEnum() == FZChannelMethod.payResultReceive && StringUtils.isNotBlank(authConfig.getCenterInfo().getPayResultReceiveUrl())) {
            reUrl = authConfig.getCenterInfo().getPayResultReceiveUrl();
        } else if (methodEnum() == FZChannelMethod.bondDownLoad && StringUtils.isNotBlank(authConfig.getCenterInfo().getBondDownLoadUrl())) {
            reUrl = authConfig.getCenterInfo().getBondDownLoadUrl();
        } else if (methodEnum() == FZChannelMethod.guaranteeBackNotice && StringUtils.isNotBlank(authConfig.getCenterInfo().getGuaranteeBackNoticeUrl())) {
            reUrl = authConfig.getCenterInfo().getGuaranteeBackNoticeUrl();
        } else if (methodEnum() == FZChannelMethod.claimResultReceive && StringUtils.isNotBlank(authConfig.getCenterInfo().getClaimResultReceiveUrl())) {
            reUrl = authConfig.getCenterInfo().getClaimResultReceiveUrl();
        }

        return reUrl;
    }

    public RESP doRequest(CenterNoEnum centerNoEnum, REQ req) {
        return this.doRequest(centerNoEnum, req, new HashMap<>());
    }

    /**
     * @param req     参与签名验签数据
     * @param attrMap 不参与签名验签附加属性
     * @return
     */
    public RESP doRequest(CenterNoEnum centerNoEnum, REQ req, Map<String, Object> attrMap) {

        FZCenterAuthConfig authConfig = fzMakeInfoConfig.getAuthConfig(centerNoEnum);

        //构建上下文
        TradeContext context = new TradeContext(req, attrMap);
        try {
            //接口公共参数设置
//            req = buildReq(req, authConfig);

            //请求参数校验
            verifyParam(context);
        } catch (Exception e) {
            CenterException ce = buildCException(InnerRespCode.FAILURE_PARAM, e, "参数错误:");
            ElgLogger.error(log, l -> l.error("traceId={} => 中心[{}][{}]服务 参数校验失败：{}", context.getTraceId(), centerNoEnum.getCenterNo(), methodEnum().getDesc(), ce.getMessage()));
            throw ce;
        }

//        JSONObject.parse

        String requestBody = this.toJsonString(req);

        //宁德中心明文传输
        //业务数据sm2公钥加密 宁德中心明文传输

        FZHeaderInfo fzHeaderInfo = FZHeaderInfo.builder()
                .appid(authConfig.getCenterInfo().getAppId())
                .requestid(IdGenerate.getIdStr())
                .timestamp(this.timestamp())
                .version(authConfig.getCenterInfo().getVersion())
                .build();

        JSONObject jsonObject = JSONObject.parseObject(requestBody);
        try {
            //签名
            String signature = authConfig.getFZAuthorization().signature(requestBody);
//            String signature = this.signature(fzHeaderInfo, authConfig, clearBizReqBody);
            fzHeaderInfo.setSign(signature);
            // 设置sign字段：加签之后的数据
            jsonObject.put("sign", signature);

        } catch (Exception e) {
            CenterException ce = buildCException(InnerRespCode.FAILURE, e, "签名异常:");
            ElgLogger.error(log, l -> l.error("traceId={} => 中心[{}][{}]服务 签名异常：{}", context.getTraceId(), centerNoEnum.getCenterNo(), methodEnum().getDesc(), ce.getMessage()));
            throw ce;
        }


        String encryptAndB64ReqBody;

        // 数据加密
        try {
//            encryptAndB64ReqBody = this.encrypt(requestBody, authConfig);
            ElgLogger.info(log, l -> l.info("traceId={} => 中心[{}][{}]服务 请求报文：{}", context.getTraceId(), centerNoEnum.getCenterNo(), methodEnum().getDesc(), jsonObject.toJSONString()));
            String encrypt = authConfig.getFZEncryption().encrypt(jsonObject.toJSONString());
            attrMap.put("param", encrypt);
        } catch (Exception e) {
            CenterException ce = buildCException(InnerRespCode.FAILURE_PARAM, e, "加密失败:");
            ElgLogger.error(log, l -> l.error("traceId={} => 中心[{}][{}]服务 参数加密失败：{}", context.getTraceId(), centerNoEnum.getCenterNo(), methodEnum().getDesc(), ce.getMessage()));
            throw ce;
        }

        //请求渠道服务
//        String reqUrl = this.buildReqUrl(authConfig);
        String reqUrl = authConfig.getCenterInfo().getApiUrl();
        try {
            REQ finalReq = req;
            ElgLogger.info(log, l -> l.info("traceId={} => 中心[{}][{}]服务 请求密文：{}", context.getTraceId(), centerNoEnum.getCenterNo(), methodEnum().getDesc(), attrMap.get("param")));
            ElgLogger.info(log, l -> l.info("traceId={} => 中心[{}][{}]服务 请求地址：{}", context.getTraceId(), centerNoEnum.getCenterNo(), methodEnum().getDesc(), reqUrl));
            HttpHeaders headers = new HttpHeaders();
            BeanMap.create(fzHeaderInfo).forEach((k, v) -> {
                headers.add((String) k, (String) v);
            });
            headers.setContentType(MediaType.MULTIPART_FORM_DATA);

            HttpEntity<Map<String, Object>> request = new HttpEntity<>(attrMap, headers);
            ResponseEntity<FZBaseRespDTO> responseEntity = restTemplate.postForEntity(reqUrl, request, FZBaseRespDTO.class);

            if (responseEntity == null || responseEntity.getBody() == null) {
                throw new RuntimeException("响应报文为空");
            } else if (!responseEntity.getStatusCode().is2xxSuccessful()) {
                throw new RuntimeException("响应报文http状态非成功[" + responseEntity.getStatusCodeValue() + ":" + responseEntity.getStatusCode().getReasonPhrase() + "]");
            } else {
                //正常响应业务处理
                FZBaseRespDTO resp = responseEntity.getBody();
                if (!HyMakeRespCodeEnum.isSuccess(resp.getCode())) {
                    throw new RuntimeException("渠道侧接收失败:[" + resp.getCode() + "," + resp.getMessage() + "]");
                }

                ElgLogger.info(log, l -> l.info("traceId={} <= 中心[{}][{}]服务 响应报文：{}", context.getTraceId(),
                        centerNoEnum.getCenterNo(), methodEnum().getDesc(), this.toJsonString(resp)));

                RESP bizRespData;
                if (resp.getData() != null) {
                    bizRespData = JSON.parseObject((String) resp.getData(), this.respClass);
                } else {
                    bizRespData = JSON.parseObject(JSON.toJSONString(resp), this.respClass);
                }
                ElgLogger.info(log, l -> l.info("traceId={} <= 中心[{}][{}]服务 响应业务数：{}", context.getTraceId(),
                        centerNoEnum.getCenterNo(), methodEnum().getDesc(), this.toJsonString(bizRespData)));
                return bizRespData;
            }


        } catch (Exception e) {
            CenterException ce = buildCException(InnerRespCode.FAILURE, e, "请求响应异常:");
            ElgLogger.error(log, l -> l.error("traceId={} <= 中心[{}][{}]服务 请求响应异常：{}", context.getTraceId(),
                    centerNoEnum.getCenterNo(), methodEnum().getDesc(), ce.getMessage()));
            throw ce;
        }


    }

    /**
     * @param req           参与签名验签数据
     * @param multiValueMap 不参与签名验签附加属性
     * @return
     */
    public RESP doRequest(CenterNoEnum centerNoEnum, REQ req, MultiValueMap<String, Object> multiValueMap) {

        FZCenterAuthConfig authConfig = fzMakeInfoConfig.getAuthConfig(centerNoEnum);

        //构建上下文
        TradeContext context = new TradeContext(req, multiValueMap);
        try {
            //接口公共参数设置
//            req = buildReq(req, authConfig);

            //请求参数校验
            verifyParam(context);
        } catch (Exception e) {
            CenterException ce = buildCException(InnerRespCode.FAILURE_PARAM, e, "参数错误:");
            ElgLogger.error(log, l -> l.error("traceId={} => 中心[{}][{}]服务 参数校验失败：{}", context.getTraceId(), centerNoEnum.getCenterNo(), methodEnum().getDesc(), ce.getMessage()));
            throw ce;
        }

//        JSONObject.parse

        String requestBody = this.toJsonString(req);

        //宁德中心明文传输
        //业务数据sm2公钥加密 宁德中心明文传输

        FZHeaderInfo fzHeaderInfo = FZHeaderInfo.builder()
                .appid(authConfig.getCenterInfo().getAppId())
                .requestid(IdGenerate.getIdStr())
                .timestamp(this.timestamp())
                .version(authConfig.getCenterInfo().getVersion())
                .build();

        JSONObject jsonObject = JSONObject.parseObject(requestBody);
        try {
            //签名
            String signature = authConfig.getFZAuthorization().signature(requestBody);
//            String signature = this.signature(fzHeaderInfo, authConfig, clearBizReqBody);
            fzHeaderInfo.setSign(signature);
            // 设置sign字段：加签之后的数据
            jsonObject.put("sign", signature);

        } catch (Exception e) {
            CenterException ce = buildCException(InnerRespCode.FAILURE, e, "签名异常:");
            ElgLogger.error(log, l -> l.error("traceId={} => 中心[{}][{}]服务 签名异常：{}", context.getTraceId(), centerNoEnum.getCenterNo(), methodEnum().getDesc(), ce.getMessage()));
            throw ce;
        }


        String encryptAndB64ReqBody;

        // 数据加密
        try {
//            encryptAndB64ReqBody = this.encrypt(requestBody, authConfig);
            ElgLogger.info(log, l -> l.info("traceId={} => 中心[{}][{}]服务 请求报文：{}", context.getTraceId(), centerNoEnum.getCenterNo(), methodEnum().getDesc(), jsonObject.toJSONString()));
//            FileSystemResource fileSystemResource = (FileSystemResource) multiValueMap.getFirst("guarantee_pdf");
//            fileSystemResource.getFilename();fileSystemResource.getPath();fileSystemResource.getFile()
//            ElgLogger.info(log, l -> l.info("traceId={} => 中心[{}][{}]服务 请求报文：{}", context.getTraceId(), centerNoEnum.getCenterNo(), methodEnum().getDesc(), ));
            String encrypt = authConfig.getFZEncryption().encrypt(jsonObject.toJSONString());
            multiValueMap.add("param", encrypt);
        } catch (Exception e) {
            CenterException ce = buildCException(InnerRespCode.FAILURE_PARAM, e, "加密失败:");
            ElgLogger.error(log, l -> l.error("traceId={} => 中心[{}][{}]服务 参数加密失败：{}", context.getTraceId(), centerNoEnum.getCenterNo(), methodEnum().getDesc(), ce.getMessage()));
            throw ce;
        }

        //请求渠道服务
//        String reqUrl = this.buildReqUrl(authConfig);
        String reqUrl = authConfig.getCenterInfo().getApiUrl();
        try {
            REQ finalReq = req;
            ElgLogger.info(log, l -> l.info("traceId={} => 中心[{}][{}]服务 请求密文：{}", context.getTraceId(), centerNoEnum.getCenterNo(), methodEnum().getDesc(), multiValueMap.getFirst("param")));
            ElgLogger.info(log, l -> l.info("traceId={} => 中心[{}][{}]服务 请求地址：{}", context.getTraceId(), centerNoEnum.getCenterNo(), methodEnum().getDesc(), reqUrl));
            HttpHeaders headers = new HttpHeaders();
            BeanMap.create(fzHeaderInfo).forEach((k, v) -> {
                headers.add((String) k, (String) v);
            });
            headers.setContentType(MediaType.MULTIPART_FORM_DATA);

            HttpEntity<MultiValueMap<String, Object>> request = new HttpEntity<>(multiValueMap, headers);
            ResponseEntity<FZBaseRespDTO> responseEntity = restTemplate.postForEntity(reqUrl, request, FZBaseRespDTO.class);

            if (responseEntity == null || responseEntity.getBody() == null) {
                throw new RuntimeException("响应报文为空");
            } else if (!responseEntity.getStatusCode().is2xxSuccessful()) {
                throw new RuntimeException("响应报文http状态非成功[" + responseEntity.getStatusCodeValue() + ":" + responseEntity.getStatusCode().getReasonPhrase() + "]");
            } else {
                //正常响应业务处理
                FZBaseRespDTO resp = responseEntity.getBody();
                ElgLogger.info(log, l -> l.info("traceId={} <= 中心[{}][{}]服务 响应原文：{}", context.getTraceId(),
                        centerNoEnum.getCenterNo(), methodEnum().getDesc(), this.toJsonString(resp)));
                String respDataStr =  toJsonString(resp.getData());
                ElgLogger.info(log, l -> l.info("traceId={} <= 中心[{}][{}]服务 响应data：{}", context.getTraceId(),
                        centerNoEnum.getCenterNo(), methodEnum().getDesc(), respDataStr));
                JSONObject data = JSONObject.parseObject(respDataStr);
                if (StringUtil.isNotBlank(data.getString("serial_num"))) {
                    resp.setCode("0");
                    resp.setMessage(data.getString("serial_num"));
                } else {
                    resp.setCode("99");
                    resp.setMessage("serial_num对象未返回");
                }
                if (!HyMakeRespCodeEnum.isSuccess(resp.getCode())) {
                    throw new RuntimeException("渠道侧接收失败:[" + resp.getCode() + "," + resp.getMessage() + "]");
                }

                RESP bizRespData;
                if (resp.getData() != null) {
                    bizRespData = JSON.parseObject(toJsonString(resp), this.respClass);
                } else {
                    bizRespData = JSON.parseObject(toJsonString(resp), this.respClass);
                }
                ElgLogger.info(log, l -> l.info("traceId={} <= 中心[{}][{}]服务 响应封装结果：{}", context.getTraceId(),
                        centerNoEnum.getCenterNo(), methodEnum().getDesc(), this.toJsonString(bizRespData)));
                return bizRespData;
            }


        } catch (Exception e) {
            CenterException ce = buildCException(InnerRespCode.FAILURE, e, "请求响应异常:");
            ElgLogger.error(log, l -> l.error("traceId={} <= 中心[{}][{}]服务 请求响应异常：{}", context.getTraceId(),
                    centerNoEnum.getCenterNo(), methodEnum().getDesc(), ce.getMessage()));
            throw ce;
        }


    }

    private String signature(FZHeaderInfo FZHeaderInfo, FZCenterAuthConfig authConfig, String clearBizReqBody) {
        return authConfig.getFZAuthorization().signature(clearBizReqBody);
    }


    /**
     * 敏感字段加密处理
     *
     * @param clearBizReqBody
     * @return
     */
    private String encrypt(String clearBizReqBody, FZCenterAuthConfig authConfig) {
        return authConfig.getFZEncryption().encrypt(clearBizReqBody);
    }

    protected CenterException buildCException(InnerRespCode innerRespCode, Exception exception, String message) {
        CenterException ce;
        if (exception instanceof SocketTimeoutException) {
            ce = CenterException.timeout("超时:" + message.concat(exception.getMessage()), exception);
        } else if (exception instanceof CenterException) {
            ce = (CenterException) exception;
        } else {
            if (exception != null) {
                ce = CenterException.exception(message.concat(exception.getMessage()), exception);
            } else {
                ce = CenterException.of(innerRespCode, message, exception);
            }
        }
        return ce;
    }

    private void verifyParam(TradeContext<REQ, RESP> context) {
        ElgLogger.debug(log, l -> l.debug("traceId={} => [{}]服务 请求参数：{}", context.getTraceId(), methodEnum().getDesc(), toJsonString(context.getReq())));
        if (StringUtils.isBlank(methodEnum().getMethod())) {
            throw CenterException.of(InnerRespCode.FAILURE_PARAM, "method参数不能为空", null);
        }
        try {
            ValidateUtil.validate(context.getReq());
        } catch (Exception e) {
            throw CenterException.of(InnerRespCode.FAILURE_PARAM, "请求参数错误", e);
        }
    }

    /**
     * 渠道方法名
     *
     * @return
     */
    protected abstract FZChannelMethod methodEnum();


    private String timestamp() {
        return String.valueOf(System.currentTimeMillis());
    }

    private String toJsonString(Object body) {
        if (body != null) {
            try {
                return JSONObject.toJSONString(body);
            } catch (Exception e) {
                throw CenterException.exception("转换json字符串异常", e);
            }
        }
        return null;
    }

    protected CenterNoEnum getCenterNoEnumByAcceptOrderNo(String acceptOrderNo) {
        return exchangeCenterService.getCenterNoEnumByAcceptOrderNo(acceptOrderNo);
    }

    protected CenterNoEnum getCenterNoEnumById(Long centerId) {
        return exchangeCenterService.getCenterNoEnumById(centerId);
    }

    protected long yuan2fenLong(String yuan) {
        try {
            return new BigDecimal(yuan).multiply(BigDecimal.valueOf(100)).longValue();
        } catch (Exception e) {
            throw CenterException.error("元转分失败", e);
        }
    }

    protected long wanYuan2fenLong(String wanYuan) {
        try {
            return new BigDecimal(wanYuan).multiply(BigDecimal.valueOf(1000000)).longValue();
        } catch (Exception e) {
            throw CenterException.error("万元转分失败", e);
        }
    }

    protected long wanYuan2yuanLong(String wanYuan) {
        try {
            return new BigDecimal(wanYuan).multiply(BigDecimal.valueOf(10000)).longValue();
        } catch (Exception e) {
            throw CenterException.error("万元转元失败", e);
        }
    }

    /**
     * @param bidBond    保证金单位分
     * @param feeRate    保费费率 默认百分几 ： 三明feeRate默认0.15%，保底300，上不封顶
     * @param minFeeYuan 保底300，上不封顶
     * @return 保费 单位分
     */
    public Long calcGuaranteeFee(Long bidBond, String feeRate, Long minFeeYuan) {
        if (bidBond == null || StringUtils.isBlank(feeRate)) {
            throw new RuntimeException("保费计算异常:保证金为空或费率为空");
        }
        //0.01% 转0.0001
        BigDecimal rate = new BigDecimal(feeRate).divide(new BigDecimal("100"), 6, RoundingMode.HALF_UP);

        BigDecimal guaranteeFee = new BigDecimal(bidBond).multiply(rate);
        Long guaranteeFeeFen = guaranteeFee.longValue();
        long minFeeFen = minFeeYuan * 100;
        if (guaranteeFeeFen < minFeeFen) {
            guaranteeFeeFen = minFeeFen;
        }
        return guaranteeFeeFen;
    }

    /**
     * 机构缓存
     */
    protected static Cache<String, OrganizationDO> orgCache = CacheBuilder.newBuilder().expireAfterWrite(5, TimeUnit.MINUTES).build();
    /**
     * 交易中心缓存：外部入口统一是db中的中心编码，对接一个内置一个不可修改
     */
    protected static Cache<String, ExchangeCenterDO> centerCache = CacheBuilder.newBuilder().expireAfterWrite(5, TimeUnit.MINUTES).build();


    protected Long getOrgId(String orgCode) {
        //TODO 后期待综合考虑
        OrganizationDO org = null;
        try {
            org = orgCache.get(orgCode, () -> {
                return MybatisDaoImpl.run().selectOne(OrganizationDO.builder().orgCode(orgCode).delFlag(DelFlagEnum.NORMAL.getValue()).build());
            });
            if (org == null) {
                ElgLogger.error(log, l -> l.error("查无此可用的机构编码[{}]", orgCode));
                throw CenterException.error("查无此可用的机构编码", null);
            }
        } catch (Exception e) {
            ElgLogger.error(log, l -> l.error("查无此可用的机构编码[{}]", orgCode, e));
            throw CenterException.exception("查无此可用的机构编码", e);
        }

        orgCache.put(orgCode, org);
        return org.getId();

    }

    /**
     * 内置交易中心编码与库表的映射
     */
    protected Long getCurCenterId(CenterNoEnum centerNoEnum) {

        ExchangeCenterDO centerDO = null;
        try {
            centerDO = centerCache.get(centerNoEnum.getCenterNo(), () -> {
                return MybatisDaoImpl.run().selectOne(ExchangeCenterDO.builder().centerCode(centerNoEnum.getCenterNo()).build());
            });
            if (centerDO == null) {
                ElgLogger.error(log, l -> l.error("查无此可用的交易中心编码[{}]", centerNoEnum.getCenterNo()));
                throw CenterException.error("查无此可用的交易中心编码", null);
            }
        } catch (Exception e) {
            ElgLogger.error(log, l -> l.error("查无此可用的交易中心编码[{}]", centerNoEnum.getCenterNo(), e));
            throw CenterException.error("查无此可用的交易中心编码", e);
        }

        centerCache.put(centerNoEnum.getCenterNo(), centerDO);
        return centerDO.getId();

    }
}
